package com.liangsui.cmall.gateway.config;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.cloud.gateway.config.GatewayProperties;
import org.springframework.cloud.gateway.route.RouteLocator;
import org.springframework.cloud.gateway.support.NameUtils;
import org.springframework.context.annotation.Primary;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Component;
import org.springframework.web.client.RestTemplate;
import springfox.documentation.swagger.web.SwaggerResource;
import springfox.documentation.swagger.web.SwaggerResourcesProvider;

import java.net.HttpURLConnection;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

@Slf4j
@Component
@Primary
@AllArgsConstructor
public class SwaggerResourceConfig implements
        SwaggerResourcesProvider {

    private final RouteLocator routeLocator;
    private final GatewayProperties gatewayProperties;

    public static final String API_URI = "v2/api-docs?group=webApi";

    @Override
    public List<SwaggerResource> get() {
        List<SwaggerResource> resources = new ArrayList<>();
        List<String> routes = new ArrayList<>();
        //获取所有路由的ID
        routeLocator.getRoutes().subscribe(route -> routes.add(route.getId()));
        //过滤出配置文件中定义的路由->过滤出Path Route Predicate->根据路径拼接成api-docs路径->生成SwaggerResource
        gatewayProperties.getRoutes().stream().filter(routeDefinition -> routes.contains(routeDefinition.getId())).forEach(route -> {
            route.getPredicates().stream()
                    .filter(predicateDefinition -> ("Path").equalsIgnoreCase(predicateDefinition.getName()))
                    .forEach(predicateDefinition -> resources.add(swaggerResource(route.getId(),
                            predicateDefinition.getArgs().get(NameUtils.GENERATED_NAME_PREFIX + "0")
                                    .replace("/api", "")
                                    .replace("**", API_URI))));
        });

        //for是自己写的过滤没有api文档的代码，视情况添加
        /*for (SwaggerResource swaggerResource : resources) {
            //获取所有服务的文档uri
            String uri = swaggerResource.getUrl();
            //获取服务名
            String serverName = uri.replace(API_URI, "");
            //拼接url
            String url = "http://localhost:88/" + serverName;
            //获取RestTemplate实例
            RestTemplate restTemplate = new RestTemplate();
            HttpHeaders httpHeaders = new HttpHeaders();
            //添加请求头
            httpHeaders.add("Content-Type", "application/json");
            httpHeaders.add("Accept", "application/json");
            //请求体
            HttpEntity<String> httpEntity = new HttpEntity<String>(null, httpHeaders);
            //发送请求获取响应
            ResponseEntity<String> responseEntity = restTemplate.exchange(url, HttpMethod.GET, httpEntity, String.class);
            String response = responseEntity.getBody();
            //解析json
            JSONObject jsonObject;
            jsonObject = JSONObject.parseObject(response);
            String str1 = jsonObject.getString("application");

            jsonObject = JSONObject.parseObject(str1);
            String str2 = jsonObject.getString("instance");

            JSONArray jsonArray = JSONObject.parseArray(str2);
            String str3 = jsonArray.getString(0);

            jsonObject = JSONObject.parseObject(str3);
            String serverUrl = jsonObject.getString("homePageUrl");
            if (null != serverUrl && !"".equals(serverUrl)) {
                //拼接服务api文档的url
                String serverApi = serverUrl + "v2/api-docs?group=webApi";
                //发送请求
                try {
                    URL url1 = new URL(serverApi);
                    HttpURLConnection httpUrlConn = (HttpURLConnection) url1.openConnection();
                    //设置连接超时时间
                    httpUrlConn.setConnectTimeout(1000);
                    //获取返回码
                    int code = httpUrlConn.getResponseCode();
                    if (code != 200) {
                        resources.remove(swaggerResource);
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }*/
        List<SwaggerResource> swagger = resources.stream().filter(res -> res.getName().contains("swagger")).collect(Collectors.toList());
        return swagger;
    }

    private SwaggerResource swaggerResource(String name, String location) {
        log.info("name:{},location:{}", name, location);
        SwaggerResource swaggerResource = new SwaggerResource();
        swaggerResource.setName(name);
        swaggerResource.setLocation(location);
        swaggerResource.setSwaggerVersion("2.0");
        return swaggerResource;
    }
}
